package com.zhichat.infrastructure.config;

import cn.hutool.core.date.DateField;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONObject;
import cn.hutool.jwt.JWT;
import cn.hutool.jwt.JWTPayload;
import cn.hutool.jwt.JWTUtil;
import com.google.common.collect.Maps;
import com.zhichat.infrastructure.constants.Constants;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import java.util.Map;
import java.util.Objects;

/**
 * @ClassName: ZhiChatUtil
 * @Description: zhichat全局Util
 * @Author: 团长九哥 https://space.bilibili.com/602197686
 * @CreateDate: 2024/12/14 17:03
 */
@Slf4j
@Component
@AllArgsConstructor
public class ZhiChatGlobalUtil {

    private final ZhiChatConfig zhiChatConfig;

    /**
     * JWT令牌的生成
     */
    public String token(Long userId) {
        //获取当前时间
        DateTime now = DateTime.now();
        //获取一段时间之后的时间
        DateTime newTime = now.offsetNew(DateField.SECOND, Constants.TOKEN_EXPIRE_TIME);
        //使用Map集合来存储载荷信息、有效期
        Map<String, Object> payloadMap = Maps.newHashMap();
        //签发时间
        payloadMap.put(JWTPayload.ISSUED_AT, now);
        //过期时间
        payloadMap.put(JWTPayload.EXPIRES_AT, newTime);
        //生效时间
        payloadMap.put(JWTPayload.NOT_BEFORE, now);
        // 负荷信息
        payloadMap.put("uId", userId);
        payloadMap.put("expire_time", newTime.getTime());
        return Constants.BEARER.concat(JWTUtil.createToken(payloadMap, zhiChatConfig.getJwtSecret().getBytes()));
    }

    /**
     * 验证token
     */
    public boolean verifyToken(String token) {
        if (StrUtil.isBlank(token)) {
            return false;
        }
        token = token.replace(Constants.BEARER, "");
        // 验证token是否正确
        if (!JWTUtil.verify(token, zhiChatConfig.getJwtSecret().getBytes())) {
            return false;
        }
        JWT jwt = JWTUtil.parseToken(token);
        // 验证是否过期
        return !jwt.validate(0);
    }

    /**
     * 获取jwt负载信息
     */
    public JSONObject getPayload(String token) {
        if (StrUtil.isBlank(token)) {
            return null;
        }
        token = token.replace(Constants.BEARER, "");
        JWT jwt = JWTUtil.parseToken(token);
        JWTPayload payload = jwt.getPayload();
        if (Objects.isNull(payload) || payload.getClaimsJson().isEmpty()) {
            return null;
        }
        return payload.getClaimsJson();
    }
}
